package com.sunseagear.wind.modules.sys.controller;

import cn.dev33.satoken.annotation.SaCheckPermission;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.sunseagear.common.base.http.R;
import com.sunseagear.common.base.http.RPage;
import com.sunseagear.common.base.mvc.controller.BaseBeanController;
import com.sunseagear.common.base.tenant.TenantProperties;
import com.sunseagear.common.utils.ObjectUtils;
import com.sunseagear.wind.common.aspectj.annotation.Log;
import com.sunseagear.wind.common.aspectj.enums.LogType;
import com.sunseagear.wind.common.utils.UserUtils;
import com.sunseagear.wind.modules.sys.dto.SetMenuPermissionDto;
import com.sunseagear.wind.modules.sys.entity.Menu;
import com.sunseagear.wind.modules.sys.entity.Role;
import com.sunseagear.wind.modules.sys.entity.query.RoleQuery;
import com.sunseagear.wind.modules.sys.service.IMenuService;
import com.sunseagear.wind.modules.sys.service.IRoleMenuService;
import com.sunseagear.wind.modules.sys.service.IRoleService;
import lombok.RequiredArgsConstructor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;


/**
 * @version V1.0
 * @package com.sunseagear.wind.modules.sys.controller
 * @title: 消息模版控制器
 * @description: 消息模版控制器 * @date: 2018-09-03 15:10:10
 * @copyright: 2018 www.sunseagear.com Inc. All rights reserved.
 */

@RestController
@RequestMapping("/sys/role")
@Log(title = "角色管理")
@RequiredArgsConstructor
public class RoleController extends BaseBeanController {

    private final IRoleService roleService;
    private final IMenuService menuService;
    private final IRoleMenuService roleMenuService;

    /**
     * 根据页码和每页记录数，以及查询条件动态加载数据
     */
    @GetMapping(value = "list")
    @Log(logType = LogType.SELECT)
    @SaCheckPermission("sys:role:list")
    public RPage<Role> list(RoleQuery query) {
        //加入条件
        QueryWrapper<Role> queryWrapper = new QueryWrapper<>();
        if (UserUtils.getUser().getTenantId().equals(TenantProperties.getInstance().getDefaultTenantId())) {
            queryWrapper.lambda().eq(Role::getTenantId, UserUtils.getTenantId());
        } else {
            queryWrapper.lambda().nested(i -> i.eq(Role::getTenantId, UserUtils.getTenantId()).or().eq(Role::getTenantId, TenantProperties.getInstance().getDefaultTenantId())).eq(Role::getIsSys, "0");
        }
        queryWrapper.lambda().orderByDesc(Role::getCreateDate)
                .like(ObjectUtils.isNotEmpty(query.getName()), Role::getName, query.getName())
                .like(ObjectUtils.isNotEmpty(query.getCode()), Role::getCode, query.getCode());
        // 预处理
        Page<Role> pageBean = roleService.page(getPage(), queryWrapper);
        return RPage.success(pageBean);
    }

    /**
     * 获取可用的用户列表
     */
    @GetMapping(value = "usable/list")
    @SaCheckPermission("sys:role:list")
    public R<List<Role>> usableLst() {
        QueryWrapper<Role> queryWrapper = new QueryWrapper<>();
        if (UserUtils.getUser().getTenantId().equals(TenantProperties.getInstance().getDefaultTenantId())) {
            queryWrapper.lambda().eq(Role::getTenantId, UserUtils.getTenantId());
        } else {
            queryWrapper.lambda().nested(i -> i.eq(Role::getTenantId, UserUtils.getTenantId()).or().eq(Role::getTenantId, TenantProperties.getInstance().getDefaultTenantId())).eq(Role::getIsSys, "0");
        }
        queryWrapper.lambda().eq(Role::getUsable, "1")
                .orderByDesc(Role::getCreateDate);
        List<Role> usableLst = roleService.list(queryWrapper);
        return R.success(usableLst);
    }

    /**
     * 添加
     *
     * @param entity 实体对象
     * @return 操作结果
     */
    @PostMapping("add")
    @Log(logType = LogType.INSERT)
    @SaCheckPermission("sys:role:add")
    public R<Void> add(@Validated @RequestBody Role entity) {
        entity.setTenantId(UserUtils.getTenantId());
        roleService.save(entity);
        return R.success("添加成功");
    }

    /**
     * 修改
     *
     * @param entity 实体对象
     * @return 操作结果
     */
    @PutMapping("update")
    @Log(logType = LogType.UPDATE)
    @SaCheckPermission("sys:role:update")
    public R<Void> update(@Validated @RequestBody Role entity) {
        roleService.saveOrUpdate(entity);
        return R.success("更新成功");
    }

    /**
     * 删除
     *
     * @param idList 主键ID
     * @return 操作结果
     */
    @DeleteMapping("delete")
    @Log(logType = LogType.DELETE)
    @SaCheckPermission("sys:role:delete")
    public R<Void> delete(@RequestBody List<Long> idList) {
        roleService.removeBatchByIds(idList);
        return R.success("删除成功");
    }

    /**
     * 通过用户ID获得角色
     */
    @PostMapping(value = "{uid}/findListByUserId")
    @SaCheckPermission("sys:role:list")
    public R<List<Role>> findListByUserId(@PathVariable("uid") Long uid) {
        return R.success(roleService.findListByUserId(uid));
    }


    /**
     * 获得菜单
     *
     * @param roleId 角色ID
     * @return 菜单
     */
    @GetMapping(value = "{roleId}/menu")
    @SaCheckPermission("sys:role:list")
    public R<Map<String, Object>> menu(@PathVariable("roleId") Long roleId) {
        Role role = roleService.getById(roleId);
        Map<String, Object> dataMap = new HashMap<>();
        List<Menu> treeNodeList;
        if ("admin".equals(role.getCode())) {
            QueryWrapper<Menu> queryWrapper = new QueryWrapper<>();
            queryWrapper.lambda().orderByAsc(Menu::getSort).ne(Menu::getType, Menu.BUTTON);
            treeNodeList = menuService.selectTreeList(queryWrapper);
        } else {
            treeNodeList = menuService.getCurrentUserMenus();
        }
        dataMap.put("menus", treeNodeList);
        // 获得选择的
        List<Menu> menuList = menuService.findMenuByRoleId(roleId);
        List<Long> menuIdList = new ArrayList<>();
        for (Menu menu : menuList) {
            menuIdList.add(menu.getId());
        }
        dataMap.put("selectMenuIds", menuIdList);
        return R.success(dataMap);
    }

    /**
     * 获得权限
     *
     * @param roleId 角色ID
     * @return 权限
     */
    @GetMapping(value = "{roleId}/permission")
    @SaCheckPermission("sys:role:list")
    public R<Map<String, Object>> permission(@PathVariable("roleId") Long roleId) {
        Role role = roleService.getById(roleId);
        Map<String, Object> dataMap = new HashMap<>();
        List<Menu> treeNodeList;
        if ("admin".equals(role.getCode())) {
            QueryWrapper<Menu> queryWrapper = new QueryWrapper<>();
            queryWrapper.lambda().orderByAsc(Menu::getSort);
            treeNodeList = menuService.selectTreeList(queryWrapper);
        } else {
            treeNodeList = menuService.findMenuAndPermissionByUserId(UserUtils.getUser().getId());
        }
        dataMap.put("menus", treeNodeList);
        // 获得选择的
        List<Menu> menuList = menuService.findPermissionByRoleId(roleId);
        List<Long> menuIdList = new ArrayList<>();
        for (Menu menu : menuList) {
            menuIdList.add(menu.getId());
        }
        dataMap.put("selectMenuIds", menuIdList);
        return R.success(dataMap);
    }

    /**
     * 菜单配置
     *
     * @param dto 设置菜单参数
     * @return 操作结果
     */
    @PostMapping(value = "/setMenu")
    @Log(logType = LogType.OTHER, title = "菜单配置")
    @SaCheckPermission("sys:role:update")
    public R<Void> setMenu(@Validated @RequestBody SetMenuPermissionDto dto) {
        roleMenuService.setMenu(dto.getRoleId(), dto.getMenuIds());
        return R.success("保存成功");
    }

    /**
     * 权限配置
     *
     * @param dto 设置权限参数
     * @return 操作结果
     */
    @PostMapping(value = "/setPermission")
    @Log(logType = LogType.OTHER, title = "权限配置")
    @SaCheckPermission("sys:role:update")
    public R<Void> setPermission(@Validated @RequestBody SetMenuPermissionDto dto) {
        roleMenuService.setPermission(dto.getRoleId(), dto.getMenuIds());
        return R.success("保存成功");
    }
}
